package com.keter.security;

import com.alibaba.fastjson.JSONObject;
import com.google.common.cache.CacheBuilder;
import com.google.common.cache.CacheLoader;
import com.google.common.cache.LoadingCache;
import com.google.common.collect.Maps;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;

import java.io.Serializable;
import java.util.Map;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.TimeUnit;

/**
 *   Security领域模型： 用于处理针对当前应用的用户相关逻辑
 */
@Service
public class SecurityService implements Serializable {

    private static final Logger logger = LoggerFactory.getLogger(SecurityService.class);

    @Value("${security.oauth2.auth-server:127.0.0.1}")
    private  String TOKEN_API;

    @Autowired
    RestTemplate restTemplate;

    /**
     * 根据token生成用户信息：每次携带认证token的请求都需要调用
     * @param token
     * @return
     */
    public UserDetailsImpl fromToken(String token) throws ExecutionException {
        return userDetailsLoadingCache.get(token);
    }

    LoadingCache<String, UserDetailsImpl> userDetailsLoadingCache = CacheBuilder.newBuilder()
            .maximumSize(1000)
            .expireAfterAccess(60, TimeUnit.MINUTES)
            .build(new CacheLoader<String, UserDetailsImpl>() {
                @Override
                public UserDetailsImpl load(String token) {
                    logger.info("我被调用了");
                    // 这里是key根据实际去取值的方法
                    return getUserDetails(token);
                }
            });

    /**
     * 从token中解析用户对象
     * @param token
     * @return
     */
    private UserDetailsImpl getUserDetails(String token) {
        Map tokenMap = Maps.newHashMap();
        tokenMap.put("token",token);
        JSONObject result = restTemplate.postForObject("http://"+TOKEN_API+"/oauth/check_token?token={1}", null, JSONObject.class,token);
        logger.debug("result:{}",result);
        return new UserDetailsImpl(
                result.getString("client_id"),
                "",
                result.getJSONArray("authorities")
        );
    }
}

